#ifndef HTTP_FORM_INCLUDED
#define HTTP_FORM_INCLUDED
#include <sys/time.h>
#include <map>
#include <string>
#include <vector>
#include <ctype.h>

using std::map;
using std::string;
using std::vector;

class HttpForm
{
public:
    int recv(int fd,const string& filedir = "./");
        // return recvd bytes,when return < 0 , error
        // filedir: when file eixist,where to store it

    string& url()
    {
        return m_url;
    }

    map<string,string>& header()
    {
        return m_head;
    }

    // field not return file info
    map<string,string>& fields()
    {
        return m_fields;
    }

    // files: img1.jpg-> /tmp/img1.jpg
    map<string,string>& files()
    {
        return m_files;
    }

    string operator[](const string& field)
    {
        map<string,string>::iterator it = m_fields.find(field);
        if ( it != m_fields.end())
            return it->second;

        it = m_files.find(field);
        if ( it != m_files.end())
            return it->second;

        return "";
    }

    void ParseBody(const string& contenttype,const char* body,int bodylen, const string& dir);
    string to_lower(const string& str)
    {
        if (str.empty())
            return str;

        unsigned i = 0;
        string tmp(str.length(),'\0');
        while ( i < str.length())
        {
            tmp[i] = char(tolower(str[i]));
            ++i;
        }
        return tmp;
    }
public:
    int stringSplit(const string& str, const string& sep, vector<string> &vec );
    // timeout: milli second
    int noblock_send(int fd, const char* buf, int len,unsigned int timeout = 0);
    int noblock_recv(int fd, char* buf, int len,unsigned int timeout = 0);
private:
    void setRecvTimeout(int fd,timeval& tval);
    void ParseHeader(const string& headstr);
    map<string,string> ReadOnePart(const string& onePart,const string& dir);
    void Parse(const string& contenttype,const char* body,int bodylen, const string& dir);

        // dir: where file is stored
private:
    map<string,string>  m_head;
    map<string,string>  m_fields;
    map<string,string>  m_files;
    string              m_url;
};


#endif
